﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Linq.Expressions;
using PhoneCore.Framework.Storage;
using SecureBox.UI.Infrastructure.Model;

namespace SecureBox.UI.Infrastructure.Data
{
    /// <summary>
    /// Represents a repository for Template entity which uses Linq DataContext
    /// </summary>
    public class TemplateRepository : IRepository<Model.Template>
    {
        private readonly SecureBoxDataContext _dataContext;

        public TemplateRepository(SecureBoxDataContext dataContext)
        {
            _dataContext = dataContext;
        }

        /// <summary>
        /// Add entity to repository
        /// </summary>
        /// <param name="entity"></param>
        public void Add(Model.Template entity)
        {
            _dataContext.Templates.InsertOnSubmit(new Template()
                            {
                                Name = entity.Name,
                                Description = entity.Description,
                                ImageUrl = entity.ImageUrl
                            });
        }

        /// <summary>
        /// Gets entity using predicate provided
        /// </summary>
        /// <param name="predicate"></param>
        /// <returns></returns>
        public Model.Template Get(Expression<Func<Model.Template, bool>> predicate)
        {
            return _dataContext.Templates.ToList()
                .Select(CreateFromData).AsQueryable().Single(predicate);
        }

        public void Update(Model.Template entity)
        {
            throw new NotImplementedException();
        }

        /// <summary>
        /// Removes entites from repository using predicate provided
        /// </summary>
        /// <param name="predicate"></param>
        public void Remove(Expression<Func<Model.Template, bool>> predicate)
        {
            var modelTemplates = (from Data.Template t in _dataContext.Templates
                                 select CreateFromData(t)).Where(predicate);

            var dataTemplates = modelTemplates.Select(t => _dataContext.Templates.Single(td => td.Id == t.Id));
            _dataContext.Templates.DeleteAllOnSubmit(dataTemplates);
        }

        /// <summary>
        /// Returns all entities from repository
        /// </summary>
        /// <returns></returns>
        public IEnumerable<Model.Template> List()
        {
            return (from Data.Template t in _dataContext.Templates
                    select CreateFromData(t));
        }

        /// <summary>
        /// Returns entitites using predicate provided
        /// </summary>
        /// <param name="predicate"></param>
        /// <returns></returns>
        public IEnumerable<Model.Template> List(Expression<Func<Model.Template, bool>> predicate)
        {
            return (from Data.Template t in _dataContext.Templates
                    select CreateFromData(t)).Where(predicate);
        }

        /// <summary>
        /// Commit changes
        /// </summary>
        public void Commit()
        {
            _dataContext.SubmitChanges();
        }

        public static Model.Template CreateFromData(Data.Template template)
        {
            return new Model.Template()
                       {
                           Id = template.Id,
                           Name = template.Name,
                           ImageUrl = template.ImageUrl,
                           Description = template.Description
                       };
        }

    }
}
